CS 기초

정수의 표현

  • 자바에서는 int를 4byte로 표현한다.
  • 32bit 중에 가장 높은 자리수의 비트는 sign bit로 사용된다. 0이면 양수 1이면 음수.
  • signed 정수의 범위는 -2147483648 ~ 2147483647 이다.
  • 양의 정수는 0x00000001 ~ 0x7fffffff(2147483647) 까지이다.
  • 음의 정수는 0xffffffff(-1) ~ 0x80000000(-2147483648) 까지이다.

    • -1을 16진수로 표현하기 위해선 0x00000001(1)에 2의 보수를 취해주면 0xffffffff이다.
    • -2을 16진수로 표현하기 위해선 0x00000002(2)에 2의 보수를 취해주면 0xfffffffe이다.(-2 이다.)
    • 이것으로 볼때 음수는 0xffffffff부터 시작해서 1씩 빠지면서 감소한다.
    • 그렇기 때문에 0x80000001은 -2147483647의 결과값이 나온다.
  • 0을 기준으로 표현한다면 0x80000000(-2147483648) ~ 0xffffffff(-1) ~ 0 ~ 0x00000001 ~ 0x7fffffff(2147483647) 이다.
  • Integer.compareUnsigned(int a, int b)의 내부를 살펴보면 Integer의 최솟값(-2147483648 = 0x80000000)을 a와 b에 각각 더해서 compare 함수를 실행한다.

    • 위의 함수는 unsigned된 int만을 사용해서 비교하는 값이다.
    • a는 -1을 b는 2를 입력해보자. 이 결과에선 -1이 나와야 하는 상황이다. ( a < b -> -1),(a > b -> 1), (a = b -> 0)
    • 그래서 음수를 입력할 경우에 -2147483648(0x80000000) + (- 1)이 되고 계산해보면 a = 0x7ffffffff(2147483647)이 된다.
    • 다음으로 그리고 다음 파라미터에는 +2를 넣어보면 0x80000000(-2147483648) + 2가 될것이고, 결과값은 b = 0x80000002(-2147483646)이 될것이다.
    • 결과값을 보면 a > b의 결과가 나오므로 1이 리턴이 되는 상황이 발생한다.
    • 이런 문제가 발생하기 때문에 반드시 signed가 아닌 unsigned 이 함수를 이용하여 정상적인 동작을 기대하기 위해선integer의 값만 넣어야한다.

양의 정수는 최대값 0x7fffffff 까지 양수이다가 +1을 하면서 0x80000000(-2147483648) 쵯소값으로 변환한다

1의 보수

이진수의 모든 자리의 숫자를 반전 시키면 1의 보수를 얻을 수 있다. 1의 보수는 대부분의 산술연산에서 원래 숫자의 음수처럼 취급된다.

00010011 - 11111100 = 00010000 이라면 값을 구하기 위해 뺄 값 (11111100) 에 1의 보수를 취하여 더해준다. 11111100 -> 00000011 이 된다.

0010011 + 0000011 = 1 00001111 의 값이 나오며, 한자릿수가 더 길어졌다. 그런 경우엔 마지막에 1을 더한 값이 결과값이다. 00001111 + 00000001 = 00010000 의 값이 된다.

하지만 부호 전환은 2의 보수보다 쉽지만, 덧셈과 뺄셈은 더 어렵다.

2의 보수

이진수의 모든 자리의 숫자를 반전 시킨 뒤 여기에 1을 더하면 2의 보수를 얻을 수 있다. 2의 보수는 대부분의 산술연산에서 원래 숫자의 음수처럼 취급된다.

01001011 의 모든 자리의 수를 반전시킨다.

10110100 (이것을 1의 보수라고 부른다)

여기에 1을 더한다. 10110100(180) + 00000001(1) = 10110101(181)

그러면 100-75 의 값을 구해보자.

100 -> 01100100 75 -> 01001011 (2의 보수로 변경) -> 10110100 + 00000001 = 10110101

01100100 + 10110101 = 1 00011001 의 결과가 나온다. 결과값은 00011001이다.

2의 보수를 사용한 연산에서 가장 높은 자리에서 자리올림이 발생하면 무시한다. 그렇기 때문에 1의 보수 보다 계산이 빠르다

소수의 표현

고정 소수점 (Fixed Point)

부호비트(1) + 정수비트(15) + 소수부비트(16) 으로 총 32비트로 이루어져 있다.

고정 소수점은 소수점을 사용하여 고정된 자리수의 소수를 나타내는 것이다. 한정된 메모리에서 부동 소수점 방식보다 좁은 범위의 수만 나타낼 수 있다.

부동 소수점의 표현 방식은 숫자를 표현하는데 있어서 일정한 유효숫자를 보장한다는 장점이 있따. 반면 고정 소수점 방식은 밑수 뿐 아니라 지수 값도 미리 결정해두고 사용하는 방식이다. 따라서 정수형 자료형을 기반으로 표현할 수 있다. 연산 장치에 따라서 부동 소수점을 지원하지 않는 경우에는 이러한 방식으로 소수점을 표현해야한다. 또한, 정수형 자료형의 연산은 부동소수점 자료형의 연산보다 빠르게 할 수 있다는 장점이 있다. 부동소수점은 곱셈이 간편하고, 소수점은 덧셈/뺄셈이 간편하다는 차이를 보인다.

부동 소수점

float은 부호비트(1) + 지수비트(8) + 가수비트(23) 으로 총 32비트로 구성되어져 있다.

float 방식은 실수를 컴퓨터 상에서 근사하여 표현할 때 소수점의 위치를 고정하지 않고 그 위치를 나타내는 수를 따로 적는 것으로, 유효숫자를 나타내는 기수와 소수점의 위치ㅡㄹ 풀이하는 지수로 나누어 표현한다.

컴퓨터에서는 고정 소수점 방식보다 넓은 범위의 수를 나타낼 수 있어 과학기술 계산에 많이 이용되지만, 근삿값으로 표현되며 고정 소수점 방식보다 연산 속도가 느리기 때문에 전용 연산 장치를 두는 경우가 많다. 고정 소수점과 달리 정수 부분과 소수 부분의 자릿수가 일정하지 않으나, 유효 숫자의 자릿수는 정해져 있다.

계산 방법

13.5를 32비트로 변환해본다.

10 진수로 표현된 정수와 소수를 32 bit의 floating 방식으로 표현하기 위해선 10진수를 2진수화 해야한다. 정수 : 13 -> 1101 8 4 2 1 -> 1101 소수 : 0.5 -> 1000 0.5 0.25 0.125. 0.625 -> 1 결과값 : 1101.1

2진수화를 한 후에는 컴퓨터가 정규화 작업을 해야한다. 소수점 자리 위로 1만 남겨놓고 모두 소수로 표현한다.

1101.1 -> 1.1011 * 2^3 로 표현할 수 있다.

그렇다면 위의 과정을 통해 다음과 같은 float 표기법의 요소를 얻을 수 있다. 부호 : 0, 지수 : 3, 가수 1101

하지만 지수는 음수와 양수로 나올 수 있는데 어떻게 표시를 할 수 있을까 ? 8비트가 나타낼 수 있는 수는 256 비트인데 이것의 대략 반인 127 을 기준으로 더했을 때 , 127보다 크면 양수, 작으면 음수로 나타낼 수 있다.

그러면 부호비트에는 0을 넣는다.

지수 비트는 3(지수값) + 127(bias)를 구하여 이진수화 하여 10000010 의 값을 얻을 수 있다. 128(1) 64(0) 32(0) 16(0) 8(0) 4(0) 2(1) 1(0) 지수비트는 10000010을 넣는다. 가수부는 1011을 가수부에 해당하는 가장 상위단부터 넣어준다.

0(부호) 10000010(지수) 10110000000000000000000(가수) 의 결과값을 얻을 수 있다.

부동소수점은 근삿값으로 표현된다

아까 소수점을 표현하기 위해서 정수와는 좀 다른 방법을 사용한 것을 잠깐 보았을 것이다. 0.75를 2진수화 시켜보면 0.11란 결과값을 얻을 수 있다. 0.5(1) 0.25(1) 0.125(0) 0.0625(0) 위에서 보면 2진수로 정확한 표현을 할 수 있는 10진수로 표현된 소수점은 0.5, 0.25, 0.125, 0.0625 … 와 같은 패턴을 가진 소수밖에 없다.

그렇다면 십진수로 표현된 0.1은 어떻게 이진수로 표현할 수 있을까 ? 근사값으로 표시를 한다. 그렇기 때문에 부동소수점은 수학적으로 정확한 계산을 하기 위해선 적합하지 않다.

출처 https://ko.wikipedia.org/wiki/%EB%B6%80%EB%8F%99%EC%86%8C%EC%88%98%EC%A0%90 위키백과 https://ko.wikipedia.org/wiki/%EA%B3%A0%EC%A0%95%EC%86%8C%EC%88%98%EC%A0₩%90 위키백과


Written by@Zero1
This blog is for that I organize what I study and my thinking, feeling and experience.

GitHub